/**
 * 
 */
package com.cnhaimei.vod.logic;

import java.util.ArrayList;
import java.util.HashMap;

import android.content.Intent;
import android.graphics.Color;
import android.os.Bundle;
import android.text.Editable;
import android.text.TextWatcher;
import android.util.Log;
import android.util.SparseArray;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.View.OnClickListener;
import android.widget.AdapterView;
import android.widget.BaseAdapter;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.AdapterView.OnItemClickListener;

import com.cnhaimei.com.PageManager;
import com.cnhaimei.com.VODLog;
import com.cnhaimei.com.PageManager.PageInfoListener;
import com.cnhaimei.vod.R;
import com.cnhaimei.vod.bean.Singer;
import com.cnhaimei.vod.bean.Song;
import com.cnhaimei.vod.logic.EventsManager.EventsListener;
import com.cnhaimei.vod.net.Request;
import com.cnhaimei.vod.net.XVod;
import com.cnhaimei.vod.net.dc.Player;
import com.cnhaimei.vod.net.dq.DQClose;
import com.cnhaimei.vod.net.dq.DQQuery;
import com.cnhaimei.vod.net.dq.DQQueryResult;
import com.cnhaimei.vod.net.dq.DQRead;
import com.cnhaimei.vod.net.dq.DQReadResult;
import com.cnhaimei.vod.net.dq.DQSinger;
import com.cnhaimei.vod.net.dq.DQSongs;
import com.cnhaimei.vod.net.dq.SingerParser;
import com.cnhaimei.vod.net.dq.SongParser;
import com.cnhaimei.vod.util.Const;
import com.cnhaimei.vod.util.Util;

/**
 * 查询搜索框
 * 
 * 规则：一定是先查询歌曲再查歌词
 * 
 * @author jin001.wu@gmail.com <br>
 * @date 2011-7-31
 * 
 */
public class SearchActivity extends VODActivity implements PageInfoListener,
		EventsListener, TextWatcher {

	private final static int REQ_CODE_MORE = 2;
	private final static int REQ_CODE_ENTER = 1;
	
	private static final String TAG = "SearchActivity";
	private static final int PAGE_SIZE = 3;
	private ListView listView;
	// private TextView curPageView;
	// private TextView totalPageView;
	private AdapterEx mListAdapter;
	private View curSelView;

	private SparseArray<ArrayList<Song>> mPageCache = new SparseArray<ArrayList<Song>>();
	private LayoutInflater mInflater;
	private PageManager pageManager;
	private ArrayList<Song> curSongList;
	private ArrayList<Singer> curSingerList;
//	private DQQueryResult querySong;
//	private DQQueryResult querySinger;

	// private long curSongSearchId;
	// private long curSingerSearchId;
	private HashMap<Long, Integer> pageSongReq = new HashMap<Long, Integer>();
	private HashMap<Long, Integer> pageSingerReq = new HashMap<Long, Integer>();
//	private long curSearchId = -1;

//	RequestQueue requestQueue = new RequestQueue();

	private boolean isNeting = false;
	private EditText seartEdit;
	private Search mSearch;
//	private int count = 0;
	private boolean beUnRegister;
	private boolean isClickedSinger;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		this.setContentView(R.layout.v8_search_list);
		
		VODLog.e(TAG, " on create");

		if (Util.DEMO) {
			curSongList = new ArrayList<Song>(42);
			for (int i = 1; i < 4; i++) {
				for (int j = 1; j < 5; j++) {
					curSongList.add(Song.createSong("寒江雪" + (i * 100 + j), "郑源"
							+ (i * 100 + j), "高清"));
				}
			}
			curSingerList = new ArrayList<Singer>();
			Singer s = new Singer();
			s.setName("张国荣");
			curSingerList.add(s);
		}
		
		pageManager = new PageManager(true);

		initView();

		pageManager.setPageButtonView(findViewById(R.id.pre),
				findViewById(R.id.next), null, null);
		pageManager.setListener(this);
		if (Util.DEMO) {
			pageManager.setPageInfo(1, 1, false);
		}

		refreshPage();
		mSearch = new Search();
		mSearch.regesiterEventsListener();
//		XVod.G().registerListener(EventsManager.Event.DISCONNECT, this);
	}
	
	@Override
	protected void onResume() {
		super.onResume();
		isClickedSinger = false;
	}

	@Override
	protected void onPause() {
		super.onPause();
		if (isFinishing()) {
			mSearch.unRegisterEventsListener();
//			XVod.G().unRegisterListener(EventsManager.Event.DISCONNECT, this);
		}
	}

	@Override
	public void onClick(View v) {
		int id = v.getId();
		switch (id) {
		case R.id.customer:
		case R.id.search:
			break;
		case R.id.goback:
			close();
			break;
		case R.id.adjus_music:
			startActivity(Const.Action.MusicSet);
			finish();
			break;
		case R.id.search_edit: {
//			if (count % 2 == 0) {
//				seartEdit.selectAll();
//			}
//			count ++;
		}
		break;
		default:
			super.onClick(v); // need parent
			break;
		}
	}

	public void onPageIndexChanged(int prePageIndex, int currentPageIndex,
			int totalPages) {
//		final ArrayList<Song> lst = mPageCache.get(currentPageIndex);
//
//		if (lst != null && lst != curSongList) {
//			curSongList = lst;
//			refreshPage();
//		}
		
		if (mSearch != null) {
			mSearch.loadData(currentPageIndex);
		}
		
		selectItem(null);
		
		// TODO

//		if (querySong != null) {
//			SongParser sp = new SongParser(querySong);
//			loadSongData(sp, currentPageIndex);
//		}
//
//		if (querySinger != null) {
//			SingerParser sp = new SingerParser(querySong, true);
//			loadSingerData(sp, currentPageIndex);
//		}
	}

	public void onPageIndexChangedError(int prePageIndex, int currentPageIndex,
			int totalPages) {
	}

	public void afterTextChanged(Editable s) {
		String search = s.toString();
		selectItem(null);
		if (search.trim().equals("")) {
//			if (querySong != null) {
//				XVod.G().closeQuery(querySong.getSnap());
//				querySong = null;
//			}
//			if (querySinger != null) {
//				XVod.G().closeQuery(querySinger.getSnap());
//				querySinger = null;
//			}
			curSongList = null;
			curSingerList = null;
			mSearch.setCurSearchNull();
			pageManager.setPageInfo(0,
					0, false);
			refreshPage();
		} else {
			Log.e(TAG, search);
			mSearch.search(search);
		}
//		count = 0;
	}

	public void beforeTextChanged(CharSequence s, int start, int count,
			int after) {
		// TODO Auto-generated method stub

	}

	public void onTextChanged(CharSequence s, int start, int before, int count) {
		// TODO Auto-generated method stub

	}

	private void initView() {
		// curPageView = (TextView) findViewById(R.id.cur_page);
		// totalPageView = (TextView) findViewById(R.id.total_page);
		
		mInflater = LayoutInflater.from(this);
		listView = (ListView) findViewById(R.id.list);
		listView.setCacheColorHint(Color.TRANSPARENT);

		seartEdit = (EditText) findViewById(R.id.search_edit);

		seartEdit.addTextChangedListener(this);
		seartEdit.setOnClickListener(this);
		
		showBackBtn(true);
		showSearchBtn(false);
		setTitle(getString(R.string.search));
	}

	private void refreshPage() {
		if (mListAdapter == null) {
			mListAdapter = new AdapterEx();
			listView.setAdapter(mListAdapter);
			listView.setOnItemClickListener(mListAdapter);
		}
		mListAdapter.setList(curSongList, curSingerList);
		// int total = pageManager.getTotalPage();
		mListAdapter.notifyDataSetChanged();
		// curPageView.setText(String.valueOf(pageManager.getCurrentIndex() +
		// 1));
		// totalPageView.setText(String.valueOf(total));
	}

//	private void search(String search) {
		// if (mCurSongQuery != null) {
		// if (mCurSongQuery.getState() == DQQuery.STATE_REQ) {
		//				
		// }
		// }
		// DQQuery songQue = new DQQuery(DQQuery.TABLE_SONG, "NAME @> \"" +
		// search + "\"");
//		requestQueue.placeRequest(new Request(DQManager.Tab_SONG, "NAME @> \""
//				+ search + "\""));
//		// curSongSearchId = XVod.G().search(DQManager.Tab_SONG, );
//		requestQueue.placeRequest(new Request(DQManager.Tab_SINGER,
//				"NAME @> \"" + search + "\""));
//		mSearch.search(search);
//	}

	private void close() {
		finish();
	}

	public class AdapterEx extends BaseAdapter implements OnItemClickListener,
			OnClickListener {

		public AdapterEx() {
		}

		ArrayList<Song> songs = new ArrayList<Song>();
		ArrayList<Singer> sings = new ArrayList<Singer>();

		public void setList(ArrayList<Song> lst, ArrayList<Singer> sing) {
			this.songs = lst;
			this.sings = sing;
		}

		public int getCount() {
			int max = songs == null ? 0 : songs.size();
			max = (sings == null || max >= sings.size()) ? max : sings.size();
			return max;
		}

		public Object getItem(int position) {
			return null;// songs.get(position);
		}

		public Song getSong(int position) {
			if (songs != null && position < songs.size()) {
				return songs.get(position);
			} else {
				return null;
			}
		}

		public Singer getSinger(int position) {
			if (sings != null && position < sings.size()) {
				return sings.get(position);
			} else {
				return null;
			}
		}

		public long getItemId(int position) {
			// TODO Auto-generated method stub
			return 0;
		}

		public View getView(int position, View convertView, ViewGroup parent) {
			ViewHolder holder = null;
			if (convertView == null) {
				//				
				convertView = mInflater.inflate(R.layout.v8_search_list_item, null);
				holder = new ViewHolder();
				holder.initView(convertView, this);
				convertView.setTag(holder);
			} else {
				holder = (ViewHolder) convertView.getTag();
			}

			holder.setValues(getSong(position), getSinger(position), position);

			return convertView;
		}

		public void onItemClick(AdapterView<?> parent, View view, int position,
				long id) {
			// TODO Auto-generated method stub
			if (isNeting) {
				return;
			}

			selectItem(view);
		}

		public void onClick(View v) {
			Object tag = v.getTag();
			if (tag instanceof Song) {
				switch (v.getId()) {
					case R.id.add:
						XVod.G().insertSong((Song) tag);
						seartEdit.selectAll();
						break;
					case R.id.insert: {
						final Player p = Player.G();
						if (p.getPlaylistCount() < Player.MAX_SEL) {
							int count = p.getPlaylistCount();
							XVod.G().insertSong((Song) tag);
							XVod.G().preSortSong(count, 1); // 1??
						}
						seartEdit.selectAll();
					}
						break;
					case R.id.singer: {
						if (!isClickedSinger) {
							isClickedSinger = true;
							StarSongsActivity.starActivity(SearchActivity.this,
									((Song) tag).getSingerName());
						}
					}
						break;
					case R.id.access:{
						startActivityForResult(new Intent(Const.Action.SelSongMore), REQ_CODE_MORE);
					}
						break;
					default:
						break;
				}
			} else if (tag instanceof Singer) {
				if (v.getId() == R.id.star) {
					if (!isClickedSinger) {
						isClickedSinger = true;
						StarSongsActivity.starActivity(SearchActivity.this,
								((Singer) tag).getName());
					}
				}
			}
		}
	}
	
	/**
	 * @param view
	 */
	private void selectItem(View view) {
		/*
		if (curSelView != null) {
			ViewHolder vhOld = (ViewHolder) curSelView.getTag();
			curSelView.setBackgroundDrawable(null);
			vhOld.singer.setSelected(false);
			vhOld.operate.setVisibility(View.INVISIBLE);
			vhOld.name.setSelected(false);
			vhOld.img1.setBackgroundResource(R.drawable.star_ico_normal);
			vhOld.img2.setBackgroundResource(R.drawable.img_normal);
		}
		curSelView = view;
		if (curSelView != null && curSelView.getTag() != null) {
			ViewHolder vh = (ViewHolder) view.getTag();
			curSelView.setBackgroundResource(R.drawable.choosing);
			vh.operate.setVisibility(View.VISIBLE);
			vh.name.setSelected(true);
			vh.singer.setSelected(true);
			vh.img1.setBackgroundResource(R.drawable.star_ico_normal);
			vh.img2.setBackgroundResource(R.drawable.img_pressed);
		}
		*/
		if (curSelView != null) {
			ViewHolder vhOld = (ViewHolder) curSelView.getTag();
			curSelView.setBackgroundDrawable(null);
			vhOld.name.setSelected(false);
		}
		curSelView = view;
		if (curSelView != null && curSelView.getTag() != null) {
			ViewHolder vh = (ViewHolder) view.getTag();
			curSelView.setBackgroundResource(R.drawable.choosing);
			vh.operate.setVisibility(View.VISIBLE);
			vh.name.setSelected(true);
		}
	}

	class ViewHolder {
		public TextView img1;
		public TextView starV;
		public TextView name;
		public TextView img2;
		public TextView singer;
		public View operate;
		public View root;
		public View addV;
		public View insertV;
		public TextView accessV;

		public ViewHolder() {
		}

		public void initView(View layout, OnClickListener click) {
			/*
			root = layout;
			img1 = (TextView) layout.findViewById(R.id.img1);
			img2 = (TextView) layout.findViewById(R.id.img2);
			starV = (TextView) layout.findViewById(R.id.star);
			name = (TextView) layout.findViewById(R.id.name);
			singer = (TextView) layout.findViewById(R.id.singer);
			addV = layout.findViewById(R.id.add);
			insertV = layout.findViewById(R.id.insert);
			operate = layout.findViewById(R.id.operate);
			starV.setOnClickListener(click);
			addV.setOnClickListener(click);
			insertV.setOnClickListener(click);
			singer.setOnClickListener(click);
			*/

			root = layout;
			name = (TextView) layout.findViewById(R.id.name);
			addV = layout.findViewById(R.id.add);
			accessV = (TextView)layout.findViewById(R.id.access);
			starV = (TextView) layout.findViewById(R.id.star);
			addV.setOnClickListener(click);
			accessV.setOnClickListener(click);
			setClickable(R.id.add, R.id.access);
		}

		public void setValues(Song song, Singer star, int pos) {
			/*
			if (star != null) {
				starV.setText(star.getName());
				starV.setTag(star);
			} else {
				starV.setText("");
				starV.setTag(null);
			}
			if (song != null) {
				name.setText(song.getName());
				singer.setText(song.getSingerName());
				addV.setTag(song);
				insertV.setTag(song);
				singer.setTag(song);
			} else {
				name.setText("");
				singer.setText("");
				addV.setTag(null);
				insertV.setTag(null);
				singer.setTag(null);
			}
			*/

			if (star != null) {
				accessV.setText(star.getName());
				accessV.setTag(star);
			} else {
				accessV.setText("");
				accessV.setTag(null);
			}
			if (song != null) {
				name.setText(song.getName());
				addV.setTag(song);
			} else {
				name.setText("");
				addV.setTag(null);
			}
		}
	}

	protected void onDQManagerDisconnect() {
		if (mSearch != null) {
			mSearch.onDisconnect();
		}
	}
	
	protected void onDQManagerReconnect() {
		if (mSearch != null) {
			mSearch.onReconnect();
		}
	}
	
	class Search implements EventsListener{
		//默认队列形式先歌曲，后歌星
		private final static int CLOSE = 0;
		private final static int OPEN = 1;
		private final static int BUSY = 2;
		private final static int IDLE = 3;
		private String curSearch;
		private String runningSearch;
		private DQQuery mCurSongQuery;
		private DQQuery mCurStarQuery;
		private DQQueryResult querySong;
		private DQQueryResult querySinger;
		private int state;
		private boolean isChange;
		private boolean autoFinish;
		
		public void search(String search) {
			if (curSearch == null || !curSearch.equals(search)) {
				isChange = true;
			}
			curSearch = search;
			search();
		}
		
		public void setCurSearchNull() {
			curSearch = null;
		}
		
		public void loadData(int pageIndex) {
			if (querySong != null && querySinger != null) {
				SongParser sp = new SongParser(querySong);
				loadSongData(sp, pageIndex);
				SingerParser sp1 = new SingerParser(querySinger, true);
				loadSingerData(sp1, pageIndex);
			}
		}
		
		public void loadSongData(SongParser sp, int pageIndex) {
			state = BUSY;
			DQRead read = new DQRead(sp);
			read.setRequest(pageIndex * PAGE_SIZE, PAGE_SIZE);
			long id = XVod.G().addRequest(read);
//			long id = XVod.G().requestRecord(sp, pageIndex * PAGE_SIZE, PAGE_SIZE);
			pageSongReq.put(id, pageIndex);
		}

		public void loadSingerData(SingerParser sp, int pageIndex) {
			state = BUSY;
			DQRead read = new DQRead(sp);
			read.setRequest(pageIndex * PAGE_SIZE, PAGE_SIZE);
			long id = XVod.G().addRequest(read);
//			long id = XVod.G().requestRecord(sp, pageIndex * PAGE_SIZE, PAGE_SIZE);
			pageSingerReq.put(id, pageIndex);
		}
		
		public void regesiterEventsListener() {
			XVod.G().registerListener(EventsManager.Event.QUERY_RESPONSE, this);
			XVod.G().registerListener(EventsManager.Event.QUERY_RECORDS, this);
			XVod.G().registerListener(EventsManager.Event.QUERY_CLOSE, this);
		}
		
		public void unRegisterEventsListener() {
			beUnRegister = true;
//			if (state == OPEN || state == BUSY) {
//				autoFinish = true;
//				if (mCurSongQuery != null
//						&& mCurSongQuery.getState() != Request.STATE_RESPONSED) {
//					mCurSongQuery.setToClose();
//				}
//				if (mCurStarQuery != null
//						&& mCurStarQuery.getState() != Request.STATE_RESPONSED) {
//					mCurStarQuery.setToClose();
//				}
//			} else if (state == IDLE){
//				closeSnap();
//			} else {
//				removeRegisterEventsListener();
//			}
			
			autoFinish = true;
			if (mCurStarQuery != null && mCurStarQuery.getState() != Request.STATE_RESPONSED) {
				mCurStarQuery.setToClose();
			}
			if (mCurSongQuery != null && mCurSongQuery.getState() != Request.STATE_RESPONSED) {
				mCurSongQuery.setToClose();
			}
			closeSnap();
			removeRegisterEventsListener();
		}
		
		public void onEvent(int event, Object obj, boolean isSuc) {
			switch (event) {
			case EventsManager.Event.QUERY_RESPONSE: {
				DQQueryResult res = (DQQueryResult) obj;
				/*
				if (isSuc) {
					if (mCurSongQuery != null
							&& mCurSongQuery.getId() == res.getId()) {
						querySong = (DQQueryResult) obj;
						mCurStarQuery = new DQQuery(DQQuery.TABLE_STAR, DQQuery
								.createStarLikeName(runningSearch));
						XVod.G().addRequest(mCurStarQuery);
					} else if (mCurStarQuery != null
							&& mCurStarQuery.getId() == res.getId()) {
						querySinger = (DQQueryResult) obj;
						pageSongReq.clear();
						pageSingerReq.clear();
						if (!autoFinish) {
							loadData(0);
							int total = Math.max(querySong.getRecordTotal(), querySinger.getRecordTotal());
							int pageCount = ( total > 0 ? total- 1: 0)
									/ PAGE_SIZE + 1;
							pageManager.setPageInfo(0,
									pageCount, false);
						} else {
							closeSnap();
						}
					}
				} else {
					if (mCurSongQuery != null && mCurSongQuery.getId() == res.getId()){
						
					}
					// Toast
					// 忽略这次查询,另起一次查询
				}
				*/
			}
				break;
			case EventsManager.Event.QUERY_RECORDS: {
				DQReadResult result = (DQReadResult) obj;
				if (isSuc && obj != null) {
					long id = result.getId();
					Integer pg = pageSongReq.get(id);
					if (pg != null) {
						DQSongs songs = (DQSongs) obj;
						// mPageCache.put(songs.getBegin(), songs.getList());
						// if (pageManager.getCurrentIndex() * PAGE_SIZE == songs
						// .getBegin()) {
						curSongList = songs.getList();
						if (!autoFinish && !isFinishing()) {
							refreshPage();
						}

					} else if (pageSingerReq.get(id) != null) {
						DQSinger singers = (DQSinger) obj;
						curSingerList = singers.getList();
						if (!autoFinish && !isFinishing()) {
							refreshPage();
						}
						
						if (isChange || autoFinish) {
							closeSnap();
						} else {
							state = IDLE;
						}
					}
				} 
				// else if fail or obj is null
			}
				break;
			case EventsManager.Event.QUERY_CLOSE: {
				if (isSuc && obj instanceof Byte) {
					int snap = (Byte) obj;
					if (querySong != null && querySinger == null && querySong.getSnap() == snap) {
						if (autoFinish) {
							removeRegisterEventsListener();
						}
					} 
					if (querySinger != null
							&& querySinger.getSnap() == snap) {
						state = CLOSE;
//						if (!autoFinish) {
						if (!beUnRegister) {
							search();
						} else {
							removeRegisterEventsListener();
						}
					}
				}
			}
			default:
				break;
			}
		}
		
		private void search() {
			if (!isChange) {
				return;
			}
			if (state == CLOSE ) {
				runningSearch = curSearch;
				if (runningSearch != null) {
					mCurSongQuery = new DQQuery(DQQuery.TABLE_SONG, DQQuery
							.createSongLikeName(runningSearch, DQQuery.QRY_SONG_ALL));
					XVod.G().addRequest(mCurSongQuery);
					state = OPEN;
				}
				isChange = false;
			} else if (state == IDLE) {
				closeSnap();
			}
		}
		
		private void removeRegisterEventsListener() {
			XVod.G().unRegisterListener(EventsManager.Event.QUERY_RECORDS, this);
			XVod.G().unRegisterListener(EventsManager.Event.QUERY_RESPONSE, this);
			XVod.G().unRegisterListener(EventsManager.Event.QUERY_CLOSE, this);
		}
		
		private void closeSnap() {
			state = BUSY;
//			if (querySong != null && mCurSongQuery != null && !mCurSongQuery.isSetToClose()) {
			if (mCurSongQuery != null && !mCurSongQuery.isSetToClose()) {
				XVod.G().addRequest(new DQClose(mCurSongQuery.getSnap()));
			}
//			if (querySinger != null && mCurStarQuery != null && !mCurStarQuery.isSetToClose()) {
			if (mCurStarQuery != null && !mCurStarQuery.isSetToClose()) {
				XVod.G().addRequest(new DQClose(mCurStarQuery.getSnap()));
			}
		}
		
		public void onDisconnect() {
			isChange = true;
			state = CLOSE;
		}
		
		public void onReconnect() {
			if (state == CLOSE && curSearch != null) {
				search();
			}
		}
	}
}
